package cn.message.shiro;

import cn.itcast.pojo.admin;
import cn.itcast.pojo.permission;
import cn.itcast.pojo.role;
import cn.message.service.IPermissionService;
import cn.message.service.IRoleService;
import cn.message.service.adminService;
import lombok.extern.slf4j.Slf4j;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.subject.Subject;
import org.springframework.context.annotation.Configuration;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Map;

/**
 * @author 郭智超
 * @create 2020-04-26 9:18
 * shiro的配置类
 */
@Configuration
@Slf4j
public class AdminRealm extends AuthorizingRealm {

    @Resource
    private adminService adminService;

    @Resource
    private IRoleService roleService;

    @Resource
    private IPermissionService permissionService;

    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        log.debug("开始执行授权逻辑-----------------");
        //获取当前用户
        Subject subject = SecurityUtils.getSubject();
        //获取认证后传过来的值
        admin admin = (admin)subject.getPrincipal();

        List<role> roleList = roleService.getRoleByAdminId(admin.getAdminId());

        //把该管理员所有的角色id存到list中
        ArrayList<Integer> roleIds = new ArrayList<>();

        for (role role : roleList) {
            //把该管理员所有的角色id存到list中
            roleIds.add(role.getRoleId());
        }

        List<permission> permissionList = permissionService.getPermissionByRoleIds(roleIds);

        //把该管理员所有的权限存到set集合中,目的是为了当该管理员拥有的两个角色都具有同种权限时，权限不重复
        HashSet<permission> permissionHashSet = new HashSet<>();
        for (permission permission : permissionList) {
            permissionHashSet.add(permission);
        }
        //给资源进行授权
        SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();

        //添加管理员的权限和角色返回前台
        for (role role : roleList) {
            //角色存储
            log.debug(role.getRole());
            authorizationInfo.addRole(role.getRole());
        }

        for (permission permission : permissionHashSet) {
            //权限存储
            log.debug(permission.getPermission().toString());
            authorizationInfo.addStringPermission(permission.getPermission());
        }
        return authorizationInfo;
    }

    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        log.debug("开始执行认证逻辑-----------------");
        //获取控制器提交的管理员输入的信息
        UsernamePasswordToken token = (UsernamePasswordToken) authenticationToken;
        cn.itcast.pojo.admin admin1 = adminService.findAdminByNickName(token.getUsername());

        if(admin1 == null){
            //用户名不存在
            return null;
        }
        if(admin1.getAdminState() == 0){
            throw new LockedAccountException();
        }

        //如果身份认证验证成功，返回一个AuthenticationInfo实现
        return new SimpleAuthenticationInfo(admin1,admin1.getAdminPassword(),"");
    }
}
